#include "FrontRibbonState.h"
#include "PlatformTypes.h"
#include "LampManager.h"

RibbonLoBeamStateMachine g_RibbonLoBeamStateMachine;

void InitRibbonLoBeamStateMachine(void)
{

    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineAgain_.sm_.Entry = RibbonLoBeamCtrlStateMachineAgainEntry;
    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineAgain_.sm_.Excute = RibbonLoBeamCtrlStateMachineAgainExcute;
    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineAgain_.sm_.Exit = RibbonLoBeamCtrlStateMachineAgainExit;
    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineAgain_.sm_.waitExitCount_ = 0;

    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOff_.sm_.Entry = RibbonLoBeamCtrlStateMachineOffEntry;
    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOff_.sm_.Excute = RibbonLoBeamCtrlStateMachineOffExcute;
    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOff_.sm_.Exit = RibbonLoBeamCtrlStateMachineOffExit;
    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOff_.sm_.waitExitCount_ = 0;

    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineInit_.sm_.Entry = RibbonLoBeamCtrlStateMachineInitEntry;
    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineInit_.sm_.Excute = RibbonLoBeamCtrlStateMachineInitExcute;
    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineInit_.sm_.Exit = RibbonLoBeamCtrlStateMachineInitExit;
    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineInit_.sm_.waitExitCount_ = 0;

    g_RibbonLoBeamStateMachine.sm_.Entry = RibbonLoBeamStateEntry;
    g_RibbonLoBeamStateMachine.sm_.Excute = RibbonLoBeamStateExcute;
    g_RibbonLoBeamStateMachine.sm_.Exit = RibbonLoBeamStateExit;
    g_RibbonLoBeamStateMachine.sm_.waitExitCount_ = 0;

    g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOn_ = &g_RibbonLoBeamCtrlStateMachine_On;
    InitRibbonLoBeamCtrlStateMachineOn();
}

static void RibbonLoBeamStateExitWithState(RibbonLoBeamStateMachine* normalStateMachine, RibbonLobeamCtrlState inputState)
{
    switch(inputState)
    {
        case RibbonLobeamCtrlState_Init:
        {
            //Ignore
            break;
        }

        case RibbonLobeamCtrlState_Off:
        {
            g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOff_.sm_.Exit();
            break;
        }

        case RibbonLobeamCtrlState_On:
        {
            g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOn_->sm_.Exit();
            break;
        }

        case RibbonLobeamCtrlState_Again:
        {
            g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineAgain_.sm_.Exit();
            break;
        }

        default:
        {
            break;
        }
    }
}

static void RibbonLoBeamStateExcuteWithState(RibbonLoBeamStateMachine* normalStateMachine, RibbonLobeamCtrlState inputState)
{
    switch(inputState)
    {
        case RibbonLobeamCtrlState_Init:
        {
                //Ignore
                break;
        }

        case RibbonLobeamCtrlState_Off:
        {
                g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOff_.sm_.Excute();
                break;
        }

        case RibbonLobeamCtrlState_On:
        {
                g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOn_->sm_.Excute();
                break;
        }

        case RibbonLobeamCtrlState_Again:
        {
                g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineAgain_.sm_.Excute();
                break;
        }

        default:
        {
                break;
        }
    }
}

static void RibbonLoBeamStateEntryWithState(RibbonLoBeamStateMachine* normalStateMachine, RibbonLobeamCtrlState inputState)
{
    switch(inputState)
    {
        case RibbonLobeamCtrlState_Init:
        {
            //Ignore
            break;
        }

        case RibbonLobeamCtrlState_Off:
        {
            g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOff_.sm_.Entry();
            break;
        }

        case RibbonLobeamCtrlState_On:
        {
            g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineOn_->sm_.Entry();
            break;
        }

        case RibbonLobeamCtrlState_Again:
        {
            g_RibbonLoBeamStateMachine.ribbonLoBeamCtrlStateMachineAgain_.sm_.Entry();
            break;
        }

        default:
        {
            break;
        }
    }
}

void RibbonLoBeamStateEntry(void)
{
    // std::cout << "RibbonLoBeamStateEntry" << std::endl;
}

void RibbonLoBeamStateExcute(void)
{
    // std::cout << "RibbonLoBeamStateExcute" << std::endl;
    if(g_FrontLastState.ribbonLobeamCtrlState_ != g_FrontNewState.ribbonLobeamCtrlState_)
    {
        RibbonLoBeamStateExitWithState(&g_RibbonLoBeamStateMachine, g_FrontLastState.ribbonLobeamCtrlState_);
        RibbonLoBeamStateEntryWithState(&g_RibbonLoBeamStateMachine, g_FrontNewState.ribbonLobeamCtrlState_);
    }
    RibbonLoBeamStateExcuteWithState(&g_RibbonLoBeamStateMachine, g_FrontNewState.ribbonLobeamCtrlState_);

    UpdateRibbonLobeamCtrlState(g_FrontNewState.ribbonLobeamCtrlState_, &g_FrontLastState.ribbonLobeamCtrlState_);
}

void RibbonLoBeamStateExit(void)
{
    // std::cout << "RibbonLoBeamStateExit" << std::endl;
    RibbonLoBeamStateExitWithState(&g_RibbonLoBeamStateMachine, g_FrontNewState.ribbonLobeamCtrlState_);

    
    g_RibbonView.model_->loBeamEffectShowSt_ = RibbonEffectShow_OFF;
    g_RibbonView.model_->loBeamEffectSt_     = RibbonEffectSel_Initial;

    UpdateRibbonLobeamCtrlState(RibbonLobeamCtrlState_Invaild, &g_FrontLastState.ribbonLobeamCtrlState_);
}


